package com.gnerv.oauth.config;

import com.gnerv.oauth.config.constant.ConfigConstant;
import com.gnerv.oauth.cuntom.*;
import com.gnerv.oauth.cuntom.login.CustomLogoutHandler;
import com.gnerv.oauth.cuntom.login.CustomSuccessHandler;
import com.gnerv.oauth.cuntom.login.CustomUsernamePasswordAuthenticationConfig;
import com.gnerv.oauth.cuntom.login.CustomUsernamePasswordAuthenticationFilter;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.method.configuration.EnableGlobalMethodSecurity;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.builders.WebSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter;
import org.springframework.security.web.authentication.rememberme.PersistentTokenRepository;

import javax.annotation.Resource;

@Configuration
@EnableGlobalMethodSecurity(securedEnabled = true, prePostEnabled = true)
public class SecurityConfig extends WebSecurityConfigurerAdapter {

    @Resource
    CustomUserDetailsService customUserDetailsService;

    //密码模式需要配置,认证管理器
    @Bean
    protected AuthenticationManager authenticationManager() throws Exception {
        return super.authenticationManager();
    }

    @Override
    protected void configure(AuthenticationManagerBuilder auth) throws Exception {
        auth.userDetailsService(customUserDetailsService);
    }

    @Bean
    CustomUsernamePasswordAuthenticationFilter customUsernamePasswordAuthenticationFilter() throws Exception {
        CustomUsernamePasswordAuthenticationFilter customUsernamePasswordAuthenticationFilter = new CustomUsernamePasswordAuthenticationFilter();
        customUsernamePasswordAuthenticationFilter.setAuthenticationManager(authenticationManager());
        customUsernamePasswordAuthenticationFilter.setAuthenticationSuccessHandler(new CustomSuccessHandler());
        return customUsernamePasswordAuthenticationFilter;
    }

    @Resource
    CustomAccessDeniedHandler customAccessDeniedHandler;
    @Resource
    CustomAuthenticationEntryPoint customAuthenticationEntryPoint;
    @Resource
    CustomLogoutHandler customLogoutHandler;
    @Resource
    CustomSuccessHandler customSuccessHandler;
    @Resource
    PersistentTokenRepository persistentTokenRepository;

    @Resource
    CustomUsernamePasswordAuthenticationConfig customUsernamePasswordAuthenticationConfig;

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http.csrf().disable()
                .apply(customUsernamePasswordAuthenticationConfig)
                .and()
                .authorizeRequests()
                //放过所有请求
                .anyRequest().permitAll()
                .and()
                .exceptionHandling()
                .authenticationEntryPoint(customAuthenticationEntryPoint)
                .accessDeniedHandler(customAccessDeniedHandler)
                .and()
                .formLogin()
                .loginPage(ConfigConstant.OAUTH_LOGIN_URL)
                .loginProcessingUrl(ConfigConstant.OAUTH_LOGIN_URL)
                .successHandler(customSuccessHandler)
                .usernameParameter("account")
                .and()
                .rememberMe()
                .tokenRepository(persistentTokenRepository)
                .tokenValiditySeconds(60 * 60 * 24)
                .and()
                .logout()
                .logoutUrl(ConfigConstant.OAUTH_LOGOUT_URL)
                .logoutSuccessHandler(customLogoutHandler);
    }

    @Override
    public void configure(WebSecurity web) throws Exception {
        web.ignoring().antMatchers("/css/**", "/js/**",
                "/index.html", "/img/**", "/fonts/**", "/favicon.ico", "/verifyCode");
    }


}
